<?php
/**
 * | 节程 [ 节程赋能开发者，助力企业发展 ]
 * +----------------------------------------------------------------------
 *  | Copyright (c) 2020~2029 温州惊蛰网络科技有限公司 All rights reserved.
 * +----------------------------------------------------------------------
 *  | Licensed 节程并不是自由软件，未经许可不能去掉节程相关版权
 * +----------------------------------------------------------------------
 */
declare (strict_types=1);

namespace app\madmin\service;

use app\madmin\model\Agent;
use app\madmin\model\Agent as admin;
use app\madmin\model\AgentApply;
use app\madmin\model\Configuration;
use app\madmin\model\User;
use app\madmin\model\view\AgentOrderProfit;
use app\madmin\model\view\AgentTeam;
use app\madmin\model\view\MallAgentTeam;
use app\utils\TrimData;
use think\Exception;
use think\facade\Db;

class AgentService
{

    /**
     * 查询列表
     * @param int $page
     * @param int $size
     * @param array $data
     * @return array
     * @throws \think\db\exception\DbException
     */
    public function findAll(array $data, int $page = 1, int $size = 10)
    {

        $admin = MallAgentTeam::field("*");

//        $admin = admin::field('id,user_id,pid,name,mobile,status,create_time,update_time')
//            ->with(['user', 'agent']);
        $admin = TrimData::searchDataTrim($admin, $data, ['name', 'mobile', 'begin_date', 'end_date']);

        $list = $admin->where($data)->paginate(['page' => $page, 'list_rows' => $size]);

        return [HTTP_SUCCESS, $list];
    }

    /**
     * 保存数据
     * @param array $data
     * @return array
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    public function save(array $data)
    {

        if (isset($data['apply_id'], $data['update_time'])) {
            $apply = AgentApply::where(['id' => $data['apply_id'], 'update_time' => $data['update_time'], 'status' => 0])
                ->update(['status' => 1]);
            if (empty($apply))
                throw new \PDOException('保存失败', HTTP_NOTACCEPT);
            unset($data['update_time']);
        }
        $agent = Db::name('agent')->where('user_id',$data['user_id'])->find();
        if (empty($agent)) {
            $model = admin::create($data);
        }else{
            Db::name('agent')->where('user_id',$data['user_id'])->update(array_merge($data,['delete_time' => null]));
            $model = admin::where('user_id',$data['user_id'])->find();
        }
        User::where('id', $data['user_id'])->update(['agent_id' => $model->id,'pid' => $model->pid]);
        return [HTTP_CREATED, $model];
    }

    /**
     * 读取一条数据
     * @param int $id
     * @return array
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    public function read(int $id)
    {
        $model = admin::with(['user', 'agent'])->find($id);
        return [HTTP_SUCCESS, $model];
    }


    /**
     * 更新数据
     * @param int $id
     * @param array $data
     * @return array
     */
    public function update(int $id, array $data)
    {
        $update_time = $data['update_time'];
        unset($data['user_id']);
        unset($data['update_time']);
        if ($data['pid'] == $id)
            throw new Exception('自己无法成为自己的下级',HTTP_NOTACCEPT);
        $count[] = Db::name('agent_team')
            ->where('id',$data['pid'])
            ->where('pid',$id)
            ->count();
        $count[] = Db::name('agent_team')
            ->where('id',$data['pid'])
            ->where('ppid',$id)
            ->count();
        $count[] = Db::name('agent_team')
            ->where('id',$data['pid'])
            ->where('pppid',$id)
            ->count();
        $count = array_sum($count);
        if ($count > 0)
            throw new Exception('下级无法成为上级',HTTP_NOTACCEPT);
        $agent = admin::where('id',(string)$id)
            ->where('update_time',(string)$update_time)
            ->find();
        $agent->save($data);
        User::where('id',$agent->user_id)->update(['pid' => $data['pid']]);
        return [HTTP_CREATED, admin::find($id)];
    }

    /**
     * @param $id
     * @return int
     */
    public function delete($id)
    {
        $agent = admin::find($id);
        if (empty($agent))
            throw new Exception('推广员不存在',HTTP_NOTACCEPT);
        admin::destroy($id);
        User::update(['agent_id' => 0,'pid' => 0],['agent_id' => $id]);
        Db::name('agent_apply')->where('user_id',$agent->user_id)->update(['delete_time' => date('Y-m-d H:i:s')]);
        return HTTP_NOCONTEND;
    }

    /**
     * @param int $page
     * @param int $size
     * @param array $post
     * @return array
     * @throws \think\db\exception\DbException
     */
    public function order(int $page, int $size, ?string $order = '',int $status = -1) : array{
        global $user;
        $agentOrderProfit = new AgentOrderProfit();
        if (!empty($order))
            $agentOrderProfit = $agentOrderProfit
                ->where('order_no','like',$order);
        if (!empty($status != -1))
            $agentOrderProfit = $agentOrderProfit
                ->where('status','=',$status);
        $list = $agentOrderProfit
            ->where('mall_id',$user['mall_id'])
            ->with(['commodityNameMaster'])
            ->order('update_time DESC')
            ->hidden(['commodity_id'])
            ->paginate(['page' => $page, 'list_rows' => $size]);
        return [HTTP_SUCCESS,$list];
    }

    /**
     * 分销团队
     * @param int $user_id
     * @param int $level
     * @param int $page
     * @param int $size
     * @return array
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    public function LevelList(int $user_id, int $level, int $page, int $size) : array{
        $field = 'id,pid,nickname,picurl,agent_total,agent_withdraw,child_agent,create_time,source';
        $agent = Agent::where('user_id',$user_id)->value('id');
        switch ($level) {
            case 1:
                $whereData = array('pid'=>$agent);
                break;
            case 2:
                $whereData = array('ppid'=>$agent);
                break;
            case 3:
                $whereData = array('pppid'=>$agent);
                break;
            case 4:
                $list = Db::name('user')
                    ->where('pid',$agent)
                    ->where('id','NOT IN',function($sql){
                        $sql->name('agent')->field('user_id')->where('delete_time','NULL');
                    })
                    ->paginate(['page' => $page, 'list_rows' => $size]);
                break;
            default:
                $list = Db::name('agent_team')
                    ->field($field.',1 AS level')
                    ->where(['pid'=>$agent]);
                $config = Configuration::where(['type' => "agentExplain"])->value("configuration");
                $config = json_decode($config, true);
                if ($config['level'] == 1) {
                    $list = $list->buildSql();
                } else if ($config['level'] == 2) {
                    $list = $list
                        ->union(function($sql1) use ($field,$agent){$sql1->name('agent_team')->field($field.',2 AS level')->where('ppid',$agent);})
                        ->buildSql();
                } else if ($config['level'] == 3) {
                    $list = $list
                        ->union(function($sql1) use ($field,$agent){$sql1->name('agent_team')->field($field.',2 AS level')->where('ppid',$agent);})
                        ->union(function($sql2) use ($field,$agent){$sql2->name('agent_team')->field($field.',3 AS level')->where('pppid',$agent);})
                        ->buildSql();
                }
                $list = Db::table($list)->alias('t')->paginate(['page' => $page, 'list_rows' => $size]);
                break;
        }
        $field .= ','.$level.' AS level';
        $list = $list ?? AgentTeam::where($whereData)
                ->field($field)
                ->paginate(['page' => $page, 'list_rows' => $size]);
        return [HTTP_SUCCESS, $list];
    }

    /**
     * 获取配置层级
     * @return array
     */
    public function rank()
    {
        $config = json_decode(Configuration::where('type','agentExplain')->value('configuration'), true);
        return [HTTP_SUCCESS, $config['level']];
    }
}
